/*
 * Sniff.java
 *
 * Created on August 21, 2007, 5:55 PM
 *
 * To change this template, choose Tools | Template Manager
 * and open the template in the editor.
 */

package org.xeerkat.xmpp.tools;

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.StringWriter;
import java.util.logging.Logger;
import org.infoset.xml.DocumentLoader;
import org.infoset.xml.Element;
import org.infoset.xml.InfosetFactory;
import org.infoset.xml.Item;
import org.infoset.xml.ItemConstructor;
import org.infoset.xml.ItemDestination;
import org.infoset.xml.XMLException;
import org.infoset.xml.sax.SAXDocumentLoader;
import org.infoset.xml.util.DocumentSource;
import org.infoset.xml.util.WriterItemDestination;
import org.xeerkat.xmpp.ClientConnection;
import org.xeerkat.xmpp.Discovery;
import org.xeerkat.xmpp.ID;
import org.xeerkat.xmpp.Protocol;
import org.xeerkat.xmpp.StanzaRouter;

/**
 *
 * @author alex
 */
public class RawChat
{
   
   static Logger LOG = Logger.getLogger(Sniff.class.getName());
   /** Creates a new instance of Sniff */
   public RawChat()
   {
   }
   
   public static void main(String [] args)
   {
      if (args.length<2) {
         System.err.println("Usage: java -jar xeerkat-xmpp-client.jar {sender} {sender-password}");
         System.exit(1);
      }
      try {
         ID id = new ID(args[0]);
         id.setPassword(args[1]);
         final ClientConnection connection = ClientConnection.lookupByDomain(id.getDomain());
         connection.connect(id);

         StanzaRouter router = new StanzaRouter();
         connection.startReceiver(router);
         router.addRoute(new ItemDestination() {
            int level = 0;
            StringWriter w;
            ItemDestination writer;
            public void send(Item item)
               throws XMLException
            {
               switch (item.getType()) {
                  case ElementItem:
                     if (level==0) {
                        w = new StringWriter();
                        writer = new WriterItemDestination(w,"UTF-8");
                     }
                     level++;
                     break;
               }
               writer.send(item);
               switch (item.getType()) {
                  case ElementEndItem:
                     level--;
                     if (level==0) {
                        LOG.info(w.toString());
                        w = null;
                        writer = null;
                     }
               }
            }
         });
         connection.sendPresence(true);
         connection.startKeepAlive();

         final Discovery discovery = new Discovery(connection,router);
         discovery.addNotifier(new Discovery.Notifier() {
            public void onDiscovery() {
               LOG.info("For "+connection.getID().getDomain());
               for (String feature : discovery.getFeatures()) {
                  LOG.info("Feature: "+feature);
               }
            }
         });
         discovery.discover();
         
         BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
         boolean stop = false;
         System.out.println("Online!");
         ItemConstructor constructor = InfosetFactory.getDefaultInfoset().createItemConstructor();
         DocumentLoader loader = new SAXDocumentLoader();
         do {
            String line = reader.readLine();
            if (line==null) {
               continue;
            }
            line = line.trim();
            if (line==null) {
               continue;
            }
            String [] parts = line.split("\\s+");
            if (parts[0].equals("exit")) {
               stop = true;
            } if (parts[0].equals("send")) {
               Element stanza = null;
               if (parts.length>1 && parts[1].charAt(0)=='<') {
                  stanza = MUC.readElement(loader,line.substring(4));

               } else {
                  String data = MUC.readData(reader);
                  stanza = MUC.readElement(loader, data);
               }
               if (stanza==null) {
                  System.err.println("No element produced!");
                  continue;
               }

               DocumentSource.generate(stanza, false, connection.getStanzaDestination());
               
            } if (parts[0].equals("data")) {
               Element dataE = null;
               if (parts.length<2) {
                  continue;
               }
               if (parts.length>2 && parts[2].charAt(0)=='<') {
                  int spaceCount = 0;
                  for (int i=parts[0].length(); Character.isWhitespace(line.charAt(i)); i++) {
                     spaceCount++;
                  }
                  dataE = MUC.readElement(loader,line.substring(parts[0].length()+spaceCount+parts[1].length()));

               } else {
                  String data = MUC.readData(reader);
                  dataE = MUC.readElement(loader, data);
               }
               if (dataE==null) {
                  System.err.println("No element produced!");
                  continue;
               }

               ItemDestination stanza = connection.getStanzaDestination();
               Element message = constructor.createElement(Protocol.MESSAGE);
               message.setAttributeValue("to",parts[1]);
               stanza.send(message);
               stanza.send(constructor.createElement(Protocol.BODY));
               stanza.send(constructor.createCharacters("data"));
               stanza.send(constructor.createElementEnd(Protocol.BODY));
               DocumentSource.generate(dataE, false, stanza);
               stanza.send(constructor.createElementEnd(Protocol.MESSAGE));

            }
         } while (!stop);
         connection.sendPresence(false);
         connection.stopKeepAlive();
         System.out.println("Disconnecting...");
         connection.disconnect();
         connection.stopReceiver();
         System.out.println("Goodbye.");
      } catch (Exception ex) {
         ex.printStackTrace();
      }
   }
   
}
